#include "animation.h"
#include "texture.h"
#include <QUndoStack>

Animation::Animation(QObject *parent)
    : AbstractObject(parent)
    , m_nCurrentFrame(0)
    , m_bLoop(true)
    , m_nXPattern(1)
    , m_nYPattern(1)
    , m_nNumFrames(1)
    , m_bSameCollisionShapeForAllFrames(false)
{
}

AnimationFrame Animation::currentFrame() const
{
    AnimationFrame frame;

    if(m_frames.size() && m_nCurrentFrame < m_frames.size())
    {
        frame = m_frames.at(m_nCurrentFrame);
    }

    return frame;
}

const AnimationFrame &Animation::frame(int nIndex) const
{
    AnimationFrame f;

    if(m_frames.size() && nIndex < m_frames.size())
    {
        f = m_frames.at(nIndex);
    }
    else
    {
        Q_ASSERT(false);
    }

    return f;
}

AnimationFrame &Animation::frame(int nIndex)
{
    if(m_frames.size() && nIndex < m_frames.size())
    {
        return m_frames[nIndex];
    }
    else
    {
        Q_ASSERT(false);
    }
}

const QList<AnimationFrame> &Animation::frames() const
{
    return m_frames;
}

void Animation::setFrame(int nIndex, const AnimationFrame &frame)
{
    if(m_frames.size() && nIndex < m_frames.size())
    {
        m_frames.replace(nIndex, frame);
    }
    else
    {
        Q_ASSERT(false);
    }
}

void Animation::generateAnimation(int xPattern, int yPattern, int nNumFrames)
{
    if(m_nXPattern == xPattern && m_nYPattern == yPattern && m_nNumFrames == nNumFrames)
    {
        return;
    }

    m_nXPattern = xPattern;
    m_nYPattern = yPattern;
    m_nNumFrames = nNumFrames;

    if(!texture())
    {
        return;
    }

    m_frames.clear();

    QPixmap pm = texture()->pixmap();
    QRect texRect = pm.rect();

    int wInc = texRect.width()/xPattern;
    int hInc = texRect.height()/yPattern;

    for(int i=0;i<nNumFrames;i++)
    {
        int hMul = i%xPattern;
        int vMul = i/xPattern;

        int startX = hMul*wInc;
        int startY = vMul*hInc;

        AnimationFrame frame;
        frame.rect = QRect(startX, startY, wInc, hInc);
        frame.csUndoStack = new QUndoStack(this);

        m_frames.append(frame);
    }
}

int Animation::xPattern() const
{
    return m_nXPattern;
}

int Animation::yPattern() const
{
    return m_nYPattern;
}

int Animation::numFrames() const
{
    return m_nNumFrames;
}

QPointer<Texture> Animation::texture() const
{
    return m_texture;
}

void Animation::setCurrentFrame(int nFrame)
{
    m_nCurrentFrame = nFrame;
    emit currentFrameChanged(nFrame);
}

void Animation::setTexture(QPointer<Texture> texture)
{
    if(m_texture == texture) return;
    m_texture = texture;
    emit textureChanged(texture);
}
